<template>
  <div>
    <div ref="chartRef" :class="props.className" :style="{ width: props.width, height: props.height }" />
  </div>
</template>

<script setup>
import { onActivated, onMounted, onBeforeUnmount, unref, ref, watch, nextTick, defineProps, markRaw } from 'vue'
import * as echarts from 'echarts'
const props = defineProps({
  // 自定义组件的类名
  className: {
    type: String,
    default: 'chart'
  },
  // 图表容器的宽度
  width: {
    type: String,
    default: '100%'
  },
  // 图表容器的高度
  height: {
    type: String,
    default: '100%'
  },
  // 图表参数
  options: {
    type: Object || undefined,
    default: undefined
  },
  // 图表是否具有点击事件
  isClick: {
    type: Boolean,
    default: false
  }
})
const chartRef = ref(null)
let chart = null
watch(
  () => props.options,
  options => {
    nextTick(() => {
      if (chart) {
        chart.setOption(options, true)
      }
    })
  },
  {
    deep: true
  }
)
const emits = defineEmits(['callbackFun'])
onMounted(() => {
  // 设置异步，不然图例一开始的宽度不正确。
  nextTick(() => {
    initChart()
  })
})
const initChart = () => {
  // 初始化echart
  const chartRefWrap = unref(chartRef)
  if (chartRefWrap) {
    chart = markRaw(echarts.init(chartRefWrap))
    // 若图表需要点击事件做些其他功能，在初始化示例时注册图表的点击事件
    if (props.isClick) {
      chart.on('click', params => {
        emits('callbackFun', params)
      })
    }
    chart.setOption(props.options, true)
    window.addEventListener('resize', chartsResize)
  }
}

onActivated(() => {
  // 防止keep-alive之后图表变形
  if (chart) {
    nextTick(() => {
      chart.resize()
    })
  }
})

const chartsResize = () => {
  chart && chart.resize()
}

onBeforeUnmount(() => {
  window.removeEventListener('resize', chartsResize)
  chart = null
})
</script>

<style lang="scss" scoped></style>
